#ifndef MONITOR_H_
#define MONITOR_H_
#include <pthread.h>
#define TRUE 1
#define FALSE 0

//Estrutura do Monitor
typedef struct monitor
{
	pthread_cond_t fornoOcupado;
	pthread_mutex_t mutex;
} Monitor;

//Estrutura do personagem.
typedef struct Personagem
{
	Monitor *m;
	int num_cliente;
	int quantidadeUsoForno; //Quantas vezes utilizou o forno
} Personagem;

int fimUsoDoForno; //Raj irá verificar se e o número desta variável é igual ao número de participantes, se sim, significa que todos já acabaram
int qtdeUsoForno; //Quantidade de vezes que cada personagem deverá usar o forno;
int jaFoiEscalonado; //Verifica se há necessidade de Raj verificar e escalonar a fila.

/*
 * Inicia estrutura Monitor.
 * Parâmetro 1: Referência para monitor
 */
void iniciaMonitor(Monitor *m);

/*
 * Procedimento para escalonar a fila de prioridade. Primeiro, ordena pela prioridade e se houver deadlock, retira o personagem com prioridade mais baixa
 * ou seja, o que possui "número mais alto". Posteriormente, ordena de acordo com a quantidade de vezes que um personagem já utilizou o forno, ou seja,
 * quem menos utilizou, fica na frente, para evitar a inanição.
 * Parâmetro 1: Referência para o mediador.
 */
void escalonarFilaUsoForno(Personagem *mediador);

/*
 * Thread para cada personagem - Cada thread significa cada personagem que demonstrará seu desejo de esquentar sua comida
 * Parâmetro 1: Referência para um personagem específico.
 */
void threadPersonagem(Personagem *personagem);

/*
 * Thread para o mediador Raj - Nesse procedimento, o mediador irá escalonar a fila de prioridade
 * Parâmetro 1: Referência para o mediador Raj
 */
void threadMediador(Personagem *mediador);

/*
 * Procedimento que indica a utilização do forno, ou seja, é aqui que algum personagem irá esquentar a comida.
 * O personagem deverá esperar a sua vez, dada uma fila de prioridade.
 * Parâmetro 1: Referência do personagem que irá utilizar o forno.
 */
void forno(Personagem *personagem);

/*
 * Procedimento para "pausar" a execução por um tempo finito randomico.
 */
void esperaRandomica();

/* Procedimento que indica o desejo de utilizar o forno pelo personagem passado por parâmetro
 * Parâmetro 1: Referência para um personagem
 */
void querUsarForno(Personagem *personagem);

/*
 * Política de DeadLock:
 * Sheldon ou Amy podem usar antes de Howard e Bernadette, que podem usar antes de
 * de Leonard e Penny, que por sua vez podem usar antes de Sheldon e Amy.
 * Como verificado, existe um grafo cíclico. Para resolver o DeadLock, basta remover um nó deste grafo.
 * O nó que removemos é do personagem Howard ou Bernadette.
 */
void verificaDeadLock();


#endif /* MONITOR_H_ */
